home *** CD-ROM | disk | FTP | other *** search
/ 130 MIDI Tool Box / 130 MIDI Tool Box.iso / mpu401 / mpuread.c < prev    next >
C/C++ Source or Header  |  1986-11-02  |  3KB  |  127 lines

  1. /* Copyright (C) 1986 by M. J. Shannon, Jr.
  2. ** Permission to distribute for non-commercial uses granted as long as this
  3. ** notice is retained.  Violators will be prosecuted.
  4. */
  5.  
  6. #include    "mpu.h"
  7.  
  8. /* midi_lengths[]:
  9. **    lengths of the MIDI voice messages after reading the 2nd byte of the
  10. **    message.
  11. */
  12.  
  13. static short midi_lengths[8] =
  14. {
  15.     1,    /* 80: Note Off */
  16.     1,    /* 90: Note On */
  17.     1,    /* A0: Note After Touch */
  18.     1,    /* B0: Control Change */
  19.     0,    /* C0: Program Change */
  20.     0,    /* D0: Channel After Touch */
  21.     1,    /* E0: Pitch Wheel */
  22.     0    /* F0: "Can't Happen" */
  23. };
  24.  
  25. /* mpu_read(char *):
  26. **    read a response from a midi device.  The response is stored in the
  27. **    passed character buffer, and the length of the response is returned.
  28. **    The buffer must be large enough to hold the response.
  29. */
  30.  
  31. int
  32. mpu_read(bp)
  33. register unsigned char *bp;
  34. {
  35.     register int length = 0;
  36.     register unsigned char data;
  37.  
  38.     if (mpu_dsr() && mpu_dsr())    /* timed out waiting for a response? */
  39.         return (length);
  40.     bp[length++] = data = mpu_dget();    /* store the input */
  41.     if (data < 0xF0)            /* time followed by midi data */
  42.     {
  43.         static unsigned char midi_rs = 0; /* last rec'd running stat */
  44.         static int mmlen;        /* and # of following bytes */
  45.         register int i;
  46.         unsigned char vm;
  47.  
  48.         vm = mpu_dget();        /* get midi voice message */
  49.         if (vm < 0x80)            /* midi running status? */
  50.             bp[length++] = midi_rs;    /* yes, store the old status */
  51.         bp[length++] = vm;        /* store the data */
  52.         if (vm <= 0xEF)            /* midi, not MPU mark */
  53.         {
  54.             if (vm >= 0x80)        /* new running status? */
  55.             {
  56.                 midi_rs = vm;    /* yes, set the new status */
  57.                 mmlen = midi_lengths[(midi_rs >> 4) & 0x07];
  58.                 bp[length++] = mpu_dget(); /* get next byte */
  59.             }
  60.             for (i = 0; i < mmlen; ++i)
  61.                 bp[length++] = mpu_dget();
  62.         }
  63.     }
  64.     else                    /* These are all MPU msgs */
  65.     switch (data)
  66.     {
  67.     case 0xF0:                /* track 1 request */
  68.     case 0xF1:                /* track 2 request */
  69.     case 0xF2:                /* track 3 request */
  70.     case 0xF3:                /* track 4 request */
  71.     case 0xF4:                /* track 5 request */
  72.     case 0xF5:                /* track 6 request */
  73.     case 0xF6:                /* track 7 request */
  74.     case 0xF7:                /* track 8 request */
  75.     case 0xF8:                /* timing overflow */
  76.     case 0xF9:                /* conductor request */
  77.     case 0xFC:                /* all end */
  78.     case 0xFD:                /* clock to host */
  79.         break;
  80.  
  81.     case 0xFF:                /* midi system message */
  82.     {
  83.         data = mpu_dget();
  84.         bp[length++] = data;
  85.         switch (data)
  86.         {
  87.         case 0xF0:            /* system exclusive */
  88.             do
  89.             {
  90.                 data = mpu_dget();
  91.                 bp[length++] = data;
  92.             }
  93.             while (data != MIDI_EOX);
  94.             break;
  95.  
  96.         case 0xF2:            /* song position pointer */
  97.             bp[length++] = mpu_dget();
  98.             /* FALL THRU */
  99.  
  100.         case 0xF3:            /* song select */
  101.             bp[length++] = mpu_dget();
  102.             /* FALL THRU */
  103.  
  104.         case 0xF6:            /* tune request */
  105.         case 0xFA:            /* start */
  106.         case 0xFB:            /* stop */
  107.         case 0xFC:            /* continue */
  108.             break;
  109.  
  110.         default:
  111.             printf("Bogus sys msg: %.2x\n", data);
  112.         }
  113.         break;
  114.     }
  115.  
  116.     case CMD_ACK:                /* we're confused.... */
  117.         printf("Spurious ACK!\n");
  118.         break;
  119.  
  120.     default:                /* we're REALLY confused.... */
  121.         printf("Bogus message: %.2x\n", data);
  122.         break;
  123.     }
  124.     return (length);
  125. }
  126.  
  127.